package com.sugo.seckill.aop;

import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Pointcut;
import org.springframework.context.annotation.Scope;
import org.springframework.core.annotation.Order;
import org.springframework.stereotype.Component;

import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;

/**
 * <p>同步锁 AOP</p>
 * @author hubin
 * @date 2020年6月10号
 * @transaction @Order(param)：param越小越是最先执行，但更重要的是最先执行的最后结束。order默认值是2147483647
 */
@Component
@Scope
@Aspect
@Order(1)
public class LockAspect {
	/**
	 * <p>互斥锁</p>
	 * <pre>
	 *  参数默认false，不公平锁
	 *  思考：
	 *  	1. 为什么不用synchronized
	 *  	2. service 默认是单例的，并发下lock只有一个实例
	 * </pre>
     */
	private static final Lock LOCK = new ReentrantLock(true);

	/**
	 * Service层切点
	 * 可以用于记录错误日志
	 */
	@Pointcut("@annotation(com.sugo.seckill.aop.ServiceLock)")
	public void lockAspect() {
		
	}

    @Around("lockAspect()")
    public  Object around(ProceedingJoinPoint joinPoint) { 
    	Object obj = null;
		LOCK.lock();
		try {
			obj = joinPoint.proceed();
		} catch (Throwable e) {
			e.printStackTrace();
			throw new RuntimeException();       
		} finally{
			LOCK.unlock();
		}
    	return obj;
    } 
}